/**
 * 通信稳定性测试脚本
 * 用于验证Node.js与PLC通信的稳定性
 */
const PLCCommunicationApp = require('./src/app');
const logger = require('./src/utils/logger');

// 创建应用实例
const app = new PLCCommunicationApp();

// 测试配置
const TEST_DURATION = 60000; // 测试持续时间（毫秒）
const READ_INTERVAL = 1000;  // 读取间隔（毫秒）
const WRITE_INTERVAL = 5000; // 写入间隔（毫秒）

// 测试统计
const stats = {
  totalReads: 0,
  successfulReads: 0,
  failedReads: 0,
  totalWrites: 0,
  successfulWrites: 0,
  failedWrites: 0,
  reconnections: 0,
  errors: []
};

// 监控重连事件
function setupMonitoring() {
  app.dataCollector.on('deviceDisconnected', (event) => {
    logger.warn(`设备断开连接: ${event.deviceId}`);
  });
  
  app.dataCollector.on('deviceConnected', (event) => {
    logger.info(`设备重新连接: ${event.deviceId}`);
    stats.reconnections++;
  });
  
  app.dataCollector.on('deviceError', (event) => {
    logger.error(`设备错误: ${event.deviceId}, ${event.error.message}`);
    stats.errors.push({
      timestamp: new Date().toISOString(),
      deviceId: event.deviceId,
      message: event.error.message
    });
  });
}

// 定期读取数据
async function scheduleReads(deviceIds) {
  const readTimer = setInterval(async () => {
    for (const deviceId of deviceIds) {
      try {
        stats.totalReads++;
        const data = await app.readAllTags(deviceId);
        stats.successfulReads++;
        logger.debug(`成功读取设备数据: ${deviceId}, 标签数: ${Object.keys(data).length}`);
      } catch (error) {
        stats.failedReads++;
        logger.error(`读取设备数据失败: ${deviceId}, ${error.message}`);
      }
    }
  }, READ_INTERVAL);
  
  return readTimer;
}

// 定期写入数据
async function scheduleWrites(deviceIds) {
  const writeTimer = setInterval(async () => {
    for (const deviceId of deviceIds) {
      try {
        // 获取设备的第一个可写标签
        const adapter = app.adapters.get(deviceId);
        if (!adapter) continue;
        
        const writableTags = Array.from(adapter.tagMap.values())
          .filter(tag => tag.type === 'coil' || tag.type === 'holdingRegister');
        
        if (writableTags.length === 0) continue;
        
        const tag = writableTags[0];
        const value = tag.dataType === 'boolean' ? Math.random() > 0.5 : Math.floor(Math.random() * 100);
        
        stats.totalWrites++;
        await app.sendCommand(deviceId, tag.name, value);
        stats.successfulWrites++;
        logger.debug(`成功写入设备数据: ${deviceId}, 标签: ${tag.name}, 值: ${value}`);
      } catch (error) {
        stats.failedWrites++;
        logger.error(`写入设备数据失败: ${deviceId}, ${error.message}`);
      }
    }
  }, WRITE_INTERVAL);
  
  return writeTimer;
}

// 打印测试结果
function printResults() {
  const readSuccessRate = stats.totalReads > 0 ? (stats.successfulReads / stats.totalReads * 100).toFixed(2) : 0;
  const writeSuccessRate = stats.totalWrites > 0 ? (stats.successfulWrites / stats.totalWrites * 100).toFixed(2) : 0;
  
  logger.info('========== 通信稳定性测试结果 ==========');
  logger.info(`测试持续时间: ${TEST_DURATION / 1000} 秒`);
  logger.info(`总读取次数: ${stats.totalReads}`);
  logger.info(`成功读取次数: ${stats.successfulReads}`);
  logger.info(`失败读取次数: ${stats.failedReads}`);
  logger.info(`读取成功率: ${readSuccessRate}%`);
  logger.info(`总写入次数: ${stats.totalWrites}`);
  logger.info(`成功写入次数: ${stats.successfulWrites}`);
  logger.info(`失败写入次数: ${stats.failedWrites}`);
  logger.info(`写入成功率: ${writeSuccessRate}%`);
  logger.info(`重连次数: ${stats.reconnections}`);
  logger.info(`错误数量: ${stats.errors.length}`);
  logger.info('========================================');
  
  return {
    duration: TEST_DURATION / 1000,
    reads: {
      total: stats.totalReads,
      successful: stats.successfulReads,
      failed: stats.failedReads,
      successRate: parseFloat(readSuccessRate)
    },
    writes: {
      total: stats.totalWrites,
      successful: stats.successfulWrites,
      failed: stats.failedWrites,
      successRate: parseFloat(writeSuccessRate)
    },
    reconnections: stats.reconnections,
    errors: stats.errors
  };
}

// 主测试函数
async function runStabilityTest() {
  try {
    logger.info('开始通信稳定性测试...');
    
    // 初始化应用
    await app.initialize();
    
    // 设置监控
    setupMonitoring();
    
    // 启动应用
    await app.start();
    
    // 获取所有设备ID
    const deviceIds = Array.from(app.adapters.keys());
    logger.info(`测试设备: ${deviceIds.join(', ')}`);
    
    // 启动定期读取和写入
    const readTimer = await scheduleReads(deviceIds);
    const writeTimer = await scheduleWrites(deviceIds);
    
    // 等待测试完成
    logger.info(`测试将持续 ${TEST_DURATION / 1000} 秒...`);
    await new Promise(resolve => setTimeout(resolve, TEST_DURATION));
    
    // 停止定时器
    clearInterval(readTimer);
    clearInterval(writeTimer);
    
    // 停止应用
    await app.stop();
    
    // 打印结果
    const results = printResults();
    
    // 返回测试结果
    return results;
  } catch (error) {
    logger.error(`测试运行错误: ${error.message}`);
    throw error;
  }
}

// 运行测试
if (require.main === module) {
  runStabilityTest()
    .then(() => {
      process.exit(0);
    })
    .catch(error => {
      logger.error(`测试失败: ${error.message}`);
      process.exit(1);
    });
} else {
  module.exports = runStabilityTest;
}
